package database;

import helperClasses.Book;
import helperClasses.ClassInfo;
import helperClasses.Member;

import java.io.EOFException;
import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.ObjectInputStream;
import java.io.ObjectOutputStream;
import java.util.Collections;
import java.util.Vector;

public class DataBaseReal implements Database
{
	protected Vector<Book> books;
	protected Vector<ClassInfo> classes;
	protected Vector<Member> members;
	
	public DataBaseReal()
	{
		books = new Vector<Book>();
		classes = new Vector<ClassInfo>();
		members = new Vector<Member>();
		
		try {
			FileInputStream inBook = new FileInputStream("books.out");
			ObjectInputStream oisBook = new ObjectInputStream(inBook);
			while(true)
			{
				books.add((Book) (oisBook.readObject()));
			}
				
		} catch (EOFException e)
		{
			
		} catch (Exception e)
		{
			System.out.println("Problem serializing: " + e);
		}
		
		try {
			FileInputStream inClass = new FileInputStream("classes.out");
			ObjectInputStream oisClass = new ObjectInputStream(inClass);
			while(true)
			{
				classes.add((ClassInfo) (oisClass.readObject()));
			}
				
		} catch (EOFException e)
		{
			
		} catch (Exception e)
		{
			System.out.println("Problem serializing: " + e);
		}
		
		try {
			FileInputStream inMem = new FileInputStream("members.out");
			ObjectInputStream oisMem = new ObjectInputStream(inMem);
			while(true)
			{
				members.add((Member) (oisMem.readObject()));
			}
				
		} catch (EOFException e)
		{
			
		} catch (Exception e)
		{
			System.out.println("Problem serializing: " + e);
		}
	}

	public boolean addBook(Book book)
	{
		return books.add(book);
	}

	public boolean deleteBook(Book book)
	{
		return books.remove(book);
	}

	public boolean addCourse(ClassInfo cla)
	{
		return classes.add(cla);
	}

	public boolean deleteCourse(ClassInfo cla)
	{
		return classes.remove(cla);
	}

	public boolean addMember(Member member) {
		return members.add(member);
	}

	public boolean isMember(String name, String password) {
		if(name == null)
		{
			return false;
		}
		if(password == null)
		{
			for(int i = 0; i < members.size(); i++)
			{
				if(members.get(i).getName().equalsIgnoreCase(name))
					return true;
			}
		}
		return members.contains(new Member(name, password));
	}

	public boolean removeMember(Member member) {
		for(int count = 0; count < members.size(); count++)
		{
			if(members.get(count).getName().equals(member.getName()))
			{
				members.remove(count);
				return true;
			}
		}
		return false;
	}
	
	public boolean updateMember(Member member) {
		
		int index;
		for(index = 0; index < members.size(); index++)
		{
			if(member.getName().equals(members.get(index).getName()))
				break;
		}

		members.remove(index);
		members.add(index, member);
		return false;
	}

	public Vector<Vector<Object>> searchBook(String search) {
		Vector<Vector<Object>> table = new Vector<Vector<Object>>();
		
		for(int count = 0; count < books.size(); count++)
		{
			Book book = books.get(count);
			if(book.getName().toLowerCase().contains(search.toLowerCase()))
			{
				table.add(book.toVector());
			}
			else if(book.getAuthor().toLowerCase().contains(search.toLowerCase()))
			{
				table.add(book.toVector());
			}
			else if(book.getISBN().contains(search.toLowerCase()))
			{
				table.add(book.toVector());
			}
		}
		return table;
	}
	
	public void onClose()
	{
		//System.out.println("INSIDE ONCLOSE");
		try {
			Collections.sort(books, new Book());
			FileOutputStream outBook = new FileOutputStream("books.out");
			ObjectOutputStream oosBook = new ObjectOutputStream(outBook);
			for(int count = 0; count < books.size(); count++)
			{
				//System.out.println("WRITING books");
				//System.out.println(books.get(count).toString());
				oosBook.writeObject(books.get(count));
			}
			oosBook.flush();
			
			Collections.sort(classes, new ClassInfo());
			FileOutputStream outClasses = new FileOutputStream("classes.out");
			ObjectOutputStream oosClasses = new ObjectOutputStream(outClasses);
			for(int count = 0; count < classes.size(); count++)
			{
				//System.out.println("WRITING classes");
				//System.out.println(classes.get(count).toString());
				oosClasses.writeObject(classes.get(count));
			}
			oosClasses.flush();
			
			Collections.sort(members, new Member());
			FileOutputStream outMembers = new FileOutputStream("members.out");
			ObjectOutputStream oosMembers = new ObjectOutputStream(outMembers);
			for(int count = 0; count < members.size(); count++)
			{
				//System.out.println("WRITING members");
				//System.out.println(members.get(count).toString());
				oosMembers.writeObject(members.get(count));
			}
			oosMembers.flush();
		} catch (EOFException e)
		{
			System.out.println("EOF: " + e);
			e.printStackTrace();
		} catch (Exception e)
		{
			System.out.println("Problem serializing: " + e);
		}
	}

	/**
	 * @param args
	 * @throws Exception 
	 */
	public static void main(String[] args) throws Exception
	{
		/*Vector<Book> table = new Vector<Book>();
		
		Vector strings = new Vector();
		
		strings.add("3");
		strings.add("2");
		strings.add("1");
		
		System.out.println("BEFORE");
		for(int count = 0; count < strings.size(); count++)
		{
			System.out.println(strings.get(count).toString());
		}
		
		Collections.sort(strings);
		System.out.println("AFTER");
		for(int count = 0; count < strings.size(); count++)
		{
			System.out.println(strings.get(count).toString());
		}
		
		
		for(int count = 0; count < 10; count++)
		{
			table.add(new Book((10- count) + "HELLO" + count, "HI", "BYE", "WHY?", 4, new Member("WHY HELLO", "WHY HELLO")));
		}
		try {
			FileOutputStream out = new FileOutputStream("books.out");
			ObjectOutputStream oos = new ObjectOutputStream(out);
			for(int count = 0; count < table.size(); count++)
			{
				System.out.println("WRITING");
				oos.writeObject(table.get(count));
			}
			oos.flush();
		} catch (Exception e) {
			System.out.println("Problem serializing: " + e);
			e.printStackTrace();
			throw e;
		}
		
		Vector<Member> tableMem = new Vector<Member>();
		
		//for(int count = 0; count < 10; count++)
		//{
			tableMem.add(new Member("rsmith@ucsd.edu", "happy"));
		//}*/
		 
		 
		 /*DataBaseReal db = new DataBaseReal();
		 
		 db.books.clear();
		 db.addBook(new Book("Hello", "Bob", "7th", "Edition", "1234567890", new Member("1", "1"), 12.75));
		 
		 db.onClose();
		
		/*try {
			FileOutputStream out = new FileOutputStream("members.out");
			ObjectOutputStream oos = new ObjectOutputStream(out);
			for(int count = 0; count < tableMem.size(); count++)
			{
				System.out.println("WRITING");
				oos.writeObject(tableMem.get(count));
			}
			oos.flush();
		} catch (Exception e) {
			System.out.println("Problem serializing: " + e);
			e.printStackTrace();
			throw e;
		}
		
		/*DataBaseReal db = new DataBaseReal();
		
		System.out.println("PRINTING BEFORE SORT");
		for(int count = 0; count < db.books.size(); count++)
		{
			System.out.println(db.books.get(count).toString());
		}
		
		Collections.sort(db.books, new Book());
		
		System.out.println("PRINTING AFTER SORT");
		for(int count = 0; count < db.books.size(); count++)
		{
			System.out.println(db.books.get(count).toString());
		}
		
		db.onClose();*/
	}

	public Member getMember(Member mem) {
		int index = members.indexOf(mem);
		
		return members.get(index).clone();
	}

	public Vector<Vector<Object>> getUserList(String name) {
		Vector<Vector<Object>> vec = new Vector<Vector<Object>>();
		for(int count = 0; count < members.size(); count++)
		{
			if(members.get(count).getName().contains(name))
				vec.add(members.get(count).toVector());
		}
		
		return vec;
	}

	public Vector<Vector<Object>> getBookList(Member member, String name) {
		Vector<Vector<Object>> vec = new Vector<Vector<Object>>();
		for(int count = 0; count < books.size(); count++)
		{
			if(books.get(count).getMember().equals(member) && books.get(count).getName().toLowerCase().contains(name.toLowerCase()))
			{
				vec.add(books.get(count).toVector());
			}
		}
		
		return vec;
	}

	public String buyBook(Book book) {
		for(int count = 0; count < books.size(); count++)
		{
			if(books.get(count).getAuthor().equals(book.getAuthor())
					&& books.get(count).getEdition().equals(book.getEdition())
					&& books.get(count).getISBN().equals(book.getISBN())
					&& books.get(count).getName().equals(book.getName())
					&& books.get(count).getQuality().equals(book.getQuality()))
			{
				return books.get(count).getMember().getEmail();
			}
		}
		return null;
	}
}
